Shell脚本与Makefile的语法区别 您所在的位置:网站首页 makefile 调用shell Shell脚本与Makefile的语法区别

Shell脚本与Makefile的语法区别

2023-03-24 16:55| 来源: 网络整理| 查看: 265

Makefile的规则是:

Target : Dependencies Commond

在Makefile中命令的部分可以调用shell脚本。但是他们的语法存在差异,很容易弄混。

一、变量的引用差异

shell脚本中所有引用以打头的变量其后要加`{shellvar},而在Makefile中的Makefile变量是以$打头的后加$(makevar),Makefile中的Shell变量(在目标执行命令中定义的变量)需要使用$${varInMakeComman}`来引用。实例如下:

# Makefile 前提是PATH是Makefile的变量。而不是shell的变量 PATH="/data/" SUBPATH=$(PATH) # Shell 脚本中 不是Makefile中shell变量的引用方式 PATH="/data/" SUBPATH=${PATH} 二、关于Makefile与Shell变量共享的问题

如果某规则有n个shell命令行构成,而相互之间没有用';'和'\'连接起来的话,就是相互之间没有关联的shell命令,相互之间也不能变量共享。

2.1 \行连接符的作用 SUBDIR=src example # 整个for循环保证是在一个shell进程完成。 all: @for subdir in $(SUBDIR); \ do\ echo "building "; \ done 没有增加行连接符,每行是一个独立的命令在独立新的Shell进程执行。 VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK) VAR_SH=limao/shell @echo "2222:"${VAR_SH} @echo "3333:"$${VAR_SH} 输出结果: 1111:limao/data/ 2222: 3333: 增加了行连接符,说明是一行语句。所以是一行输出 VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK) \ VAR_SH=limao/shell \ @echo "2222:"${VAR_SH} \ @echo "3333:"$${VAR_SH} 输出结果: 1111:limao/data/ @VAR_SH=limao/shell @echo 2222: @echo 3333: 只增加分号;,发现与不加分号是一样的结果。 VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK); @VAR_SH=limao/shell; @echo "2222:"${VAR_SH}; @echo "3333:"$${VAR_SH}; 输出结果: 1111:limao/data/ 2222: 3333: ';'和'\'一起使用 正确 VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK);\ @VAR_SH=limao/shell;\ @echo "2222:"${VAR_SH};\ @echo "3333:"$${VAR_SH}; 输出结果: 1111:limao/data/ /bin/sh: @VAR_SH=limao/shell: No such file or directory /bin/sh: @echo: command not found /bin/sh: @echo: command not found make: *** [all] Error 127 错误分析:shell中并不能对@echo 进行解析。实际上只有Makefile可以对此进行解析。但问题是为何上面3个示例@echo 可以被解析呢? VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK);\ VAR_SH=limao/shell;\ echo "2222:"${VAR_SH};\ echo "3333:"$${VAR_SH}; 输出结果: 1111:limao/data/ 2222: 3333:limao/shell VAR_MK=limao/data/ all: @echo "1111:"$(VAR_MK);\ VAR_SH=limao/shell;\ VAR_MK=limao/data/data2; \ echo "2222:"${VAR_SH};\ echo "3333:"$${VAR_SH}; \ echo "4444:"${VAR_MK};\ echo "5555:"$${VAR_MK}; 输出结果: 1111:limao/data/ 2222: 3333:limao/shell 4444:limao/data/ 5555:limao/data/data2

结论:

Makefile中的变量与Shell中变量是独立的。Makefile变量通过(var)方式取得变量值;Shell变量在Makefile中的目标命令执行下定义,并通过$${var}的方式取得其值,而不能通过{var},需要两个$$才能解析。 Makefile的目标命令下;所有的命令如果想要共享Shell变量值,那么必须所有Shell命令的执行是在同一个Shell进行去执行,也就是要通过; \符号去连接每一个命令。否则,每条命令都是在独立的新的Shell进程执行,Shell变量就不会共享。Makefile中所有以$打头的单词都会被解释成Makefile中的变量。如果你需要调用shell中的变量(或者正则表达式中锚定句位),都需要加两个符号($$)。在纯Shell脚本中,表示当前Shell进程的ID号。`{var}或$$var最终 shell 看到的是$var` 三、关于Makefile中@command语句的回显 在shell脚本中@echo的用法不能被解析的。@echo提示不可知的命令。因为不存在这样的一个命令。 在shell中echo "limao"输出就是"limao",并不会打印命令的回显, 如打印echo "limao"。 shell本身不能解析@echo;shell不存在回显的情况;

但是在Makefile文件中,因为Makefile文件会先整个被load到Make去分析一遍,然后依次构建目标与依赖,并解析执行目标的命令语句。而这个@命令可以在这个阶段被解析出来。

在Makefile中@echo是可以被解析的,这就是Makefile与shell的区别之一。 @echo “limao"会打印命令的回显。 @echo能被Makefile解析,@echo和echo都能正常执行命令;@echo会回显命令,echo不回显命令。 对于Makefile来说,要打印回显,在命令前加上@即可,不确定是否所有命令都支持@回显。 四、通配符区别 shell 中通配符*表示所有的字符 Makefile 中通配符%表示所有的字符 五、在Makefile中只能在规则的comman中使用Shell命令或脚本,其他地方不能。

比如如下代码就是没有任何输出:

VAR="Hello" echo "$VAR" all:

以上代码任何时候都不会输出,没有在target内,如果上述代码改为如下:

VAR="Hello" all: echo "$VAR"

以上代码,在make all的时候将会执行echo命令。

六、获取当前目录

PATH=pwd 注意是``, 不是''



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有